home *** CD-ROM | disk | FTP | other *** search
/ SGI Developer Toolbox 6.1 / SGI Developer Toolbox 6.1 - Disc 4.iso / src / demos / GL / libdemo / options.c++ < prev    next >
Encoding:
C/C++ Source or Header  |  1994-08-02  |  4.6 KB  |  260 lines

  1. /*
  2.  * Copyright 1991, 1992, 1993, 1994, Silicon Graphics, Inc.
  3.  * All Rights Reserved.
  4.  *
  5.  * This is UNPUBLISHED PROPRIETARY SOURCE CODE of Silicon Graphics, Inc.;
  6.  * the contents of this file may not be disclosed to third parties, copied or
  7.  * duplicated in any form, in whole or in part, without the prior written
  8.  * permission of Silicon Graphics, Inc.
  9.  *
  10.  * RESTRICTED RIGHTS LEGEND:
  11.  * Use, duplication or disclosure by the Government is subject to restrictions
  12.  * as set forth in subdivision (c)(1)(ii) of the Rights in Technical Data
  13.  * and Computer Software clause at DFARS 252.227-7013, and/or in similar or
  14.  * successor clauses in the FAR, DOD or NASA FAR Supplement. Unpublished -
  15.  * rights reserved under the Copyright Laws of the United States.
  16.  */
  17. #include <stdio.h>
  18. #include <libc.h>
  19. #include <string.h>
  20.  
  21. #include "options.h"
  22.  
  23. option * option::head = 0;
  24. char option::optString[256];
  25.  
  26. char * appName;
  27.  
  28. commandArgument * theCommandArgument;
  29.  
  30.  
  31. option::option(int o, char * d)
  32. {
  33.     opt = o;
  34.     description = d;
  35.     given = 0;
  36.  
  37.     if (o) {        // if its a real option
  38.     char buff[2];        // append to getopt string
  39.     buff[0] = o;
  40.     buff[1] = 0;
  41.     strcat(optString, buff);
  42.  
  43.     next = head;        // add self to list of options
  44.     head = this;
  45.     }
  46. }
  47.  
  48. int
  49. option::wasGiven()
  50. {
  51.     return given;
  52. }
  53.  
  54. void
  55. option::usage()
  56. {
  57.     fprintf(stderr, "  -%c     %s\n", opt, description);
  58. }
  59.  
  60. int
  61. option::checkOption(int o, char *)
  62. {
  63.     if (o == opt)
  64.     given = 1;
  65.     
  66.     return (o == opt);
  67. }
  68.  
  69.  
  70. stringOption::stringOption(int o, char * d, char * defaultIn)
  71.     : option(o, d)
  72. {
  73.     arg = defaultIn;
  74.  
  75.     char buff[2];    // append a colon to the getopt string, telling getopt
  76.     buff[0] = ':';    // this option (added to optString in option construct)
  77.     buff[1] = 0;    // takes an argument.
  78.     strcat(optString, buff);
  79. }
  80.  
  81. char *
  82. stringOption::getArgument()
  83. {
  84.     return arg;
  85. }
  86.  
  87. int
  88. stringOption::checkOption(int o, char * a)
  89. {
  90.     if (o == opt) {
  91.     given = 1;
  92.     arg = a;
  93.     }
  94.  
  95.     return (o == opt);
  96. }
  97.  
  98.  
  99. manyArgsOption::manyArgsOption(int o, char * d, char * defaultIn, int n)
  100.     : stringOption(o, d, defaultIn)
  101. {
  102.     expected = n;
  103.     received = 0;
  104.     args = 0;
  105. }
  106.  
  107. char *
  108. manyArgsOption::getArg(int n)
  109. {
  110.     if (args == 0)
  111.     parse();
  112.  
  113.     if (n >= received) {
  114.     usage();
  115.     fprintf(stderr, "Error:  %d argument(s) requested, only received %d\n",
  116.         n +1, received);
  117.     exit(1);
  118.     }
  119.  
  120.     return args[n];
  121. }
  122.  
  123. int 
  124. manyArgsOption::getNumber() 
  125.     if (args == 0)
  126.     parse();
  127.  
  128.     return received;
  129. }
  130.  
  131. void
  132. manyArgsOption::parse()
  133. {
  134.     args = new char *[expected];
  135.  
  136.     if (getArgument() == 0)
  137.     return;
  138.  
  139.     char * scan = strdup(getArgument());
  140.     char * t;
  141.     while (t = strtok(scan, ", ")) {
  142.     if (received == expected) {
  143.         usage();
  144.         fprintf(stderr, "Error:  Too many arguments (max is %d)\n",
  145.             expected);
  146.         exit(1);
  147.     }
  148.  
  149.     args[received++] = t;
  150.     scan = 0;
  151.     }
  152. }
  153.  
  154.  
  155. commandArgument::commandArgument(char * desc, int n)
  156. {
  157.     args = 0;
  158.     description = desc;
  159.     expected = n;
  160.     received = 0;
  161.  
  162.     theCommandArgument = this;
  163. }
  164.  
  165. int commandArgument::getNumber()
  166. {
  167.     return received;
  168. }
  169.  
  170. char * commandArgument::getArg(int n)
  171. {
  172.     if (n >= received) {
  173.     fprintf(stderr, 
  174.             "%s:  Error:  %s (argument %d) not specified.\n",
  175.             appName, description, n + 1);
  176.     exit(1);
  177.     }
  178.  
  179.     return args[n];
  180. }
  181.  
  182. int commandArgument::setArgument(int n, char ** a)
  183. {
  184.     if (n > expected) {
  185.     fprintf(stderr, "%s:  arguments received is %d, only expecting %d.\n",
  186.             description, n, expected);
  187.     return 0;                // return error
  188.     }
  189.  
  190.     received = n;
  191.     args = a;
  192.     return 1;        // ok.
  193. }
  194.  
  195. void
  196. commandArgument::usage()
  197. {
  198.     fprintf(stderr, "%s\n", description);
  199. }
  200.  
  201.  
  202. class processOptions : public option
  203. {
  204. public:
  205.     processOptions(int, char **);
  206. };
  207.  
  208. processOptions::processOptions(int argc, char ** argv)
  209.     : option(0, 0)
  210. {
  211.     int opt, err = 0;
  212.     option * i;
  213.     
  214.     if ((appName = strrchr(argv[0], '/')) == 0)
  215.     appName = argv[0];
  216.  
  217.     while ((opt = getopt(argc, argv, optString)) != -1)
  218.     if (opt == '?')
  219.         err++;
  220.     else
  221.     {
  222.         int gotten = 0;
  223.         
  224.         for (i = head; i ; i = i->next)
  225.         if (i->checkOption(opt, optarg))
  226.             gotten = 1;
  227.         if (!gotten)
  228.         err++;
  229.     }
  230.  
  231.     if (!err && (theCommandArgument != 0))
  232.     if (theCommandArgument->setArgument(argc - optind, argv + optind) == 0)
  233.         err++;
  234.  
  235.     if (err) {
  236.     fprintf(stderr, "Usage:  %s [options] %s\n", appName,
  237.         theCommandArgument ? theCommandArgument->description : "");
  238.     fputs("options:\n", stderr);
  239.  
  240.     for (i = head; i ; i = i->next)
  241.         i->usage();
  242.  
  243.     exit(1);
  244.     }
  245.  
  246.     Main();
  247. }
  248.  
  249.  
  250. /*
  251.  * This is the real main that processes all the command line options.
  252.  * the user defined "Main" is called after this.
  253.  */
  254. int
  255. main(int argc, char ** argv)
  256. {
  257.     processOptions p(argc, argv);
  258. }
  259.